package com.mytest.provider.service.config.security.jwt;

import com.alibaba.fastjson.JSONObject;
import com.google.common.collect.Lists;
import com.myrest.provider.poi.work.entities.user.SysUser;
import com.mytest.common.constant.SecurityConstant;
import com.mytest.common.jwt.JwtUtil;
import com.mytest.common.result.ResponseUtil;
import io.jsonwebtoken.Claims;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.security.authentication.AuthenticationManager;
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
import org.springframework.security.core.GrantedAuthority;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.security.core.userdetails.User;
import org.springframework.security.web.authentication.www.BasicAuthenticationFilter;

import javax.servlet.FilterChain;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.util.List;

/**
 * Jwt认证过滤器
 *
 * @author cxb
 * @date 2019-07-29 15:26
 */
@Slf4j
public class JwtAuthenticationFilter extends BasicAuthenticationFilter {


    @Autowired
    RedisTemplate redisTemplate;

    public JwtAuthenticationFilter(AuthenticationManager authenticationManager) {
        super(authenticationManager);
    }

    /**
     * 判断请求是否符合要求,符合要求的将用户的信息+权限存储到Authentication里面,最终存入securitycontextHolder里面去
     * @param request
     * @param response
     * @param chain
     * @throws IOException
     * @throws ServletException
     */
    @Override
    protected void doFilterInternal(HttpServletRequest request, HttpServletResponse response, FilterChain chain) throws IOException, ServletException {
        String token = request.getHeader(SecurityConstant.HEADER);
        if (StringUtils.isBlank(token)) {
            token = request.getParameter(SecurityConstant.HEADER);
        }
        if (StringUtils.isBlank(token) || !token.startsWith(SecurityConstant.TOKEN_SPLIT)) {
            chain.doFilter(request, response);
            return;
        }

        String uri = request.getRequestURI();
        String prefix = "/admin";
        if (StringUtils.startsWith(uri, prefix)) {
            try {
                UsernamePasswordAuthenticationToken authenticationToken = getAuthentication(request, response);
                //将用户信息+权限存入Authentication中
                SecurityContextHolder.getContext().setAuthentication(authenticationToken);
            } catch (Exception e) {

            }
        }
        //如果不符合要求就调用下一个filter
        chain.doFilter(request, response);
    }

    private UsernamePasswordAuthenticationToken getAuthentication(HttpServletRequest request, HttpServletResponse response) {
        String token1 = request.getHeader(SecurityConstant.HEADER);
        String token = null;

        try {
            // 获取redis里的token
            token = (String)redisTemplate.opsForValue().get(token1);

            // 获取Redis里面的ip
            String ip = (String)redisTemplate.opsForValue().get(token1+"Ip");
            String[] split1 = ip.split(",");
            ip = split1[0];
            String ipAddress = request.getHeader("X-Real-IP");
            String[] split2 = ipAddress.split(",");
            ipAddress = split1[0];
            System.out.println("ipAddress::"+ipAddress);
            if (!ip.equals(ipAddress)){
                ResponseUtil.out(response, ResponseUtil.resultMap(false, 500, "非正常登录,请重新登录"));
            }
            System.out.println("kkkkkkkkkkk");
        } catch (Exception e) {
            System.out.println("lllllllllll");
            ResponseUtil.out(response, ResponseUtil.resultMap(false, 500, "非正常登录"));
        }

        if (StringUtils.isNotBlank(token)) {
            //解析token
            Claims claims = null;
            try {
                claims = JwtUtil.parseJwt(token);
                String userInfo = claims.getSubject();
                SysUser sysUser = JSONObject.parseObject(userInfo, SysUser.class);
                String username = sysUser.getUsername();
                //获取权限  TODO token里面没有权限信息
                //GrantedAuthority接口 表示授予对象的权限
                List<GrantedAuthority> authorities = Lists.newArrayList();
                System.out.println("Claims :::::::::::"+claims);
//                String authority = claims.get(SecurityConstant.AUTHORITIES).toString();

                /*if (StringUtils.isNotBlank(authority)) {
                    List<String> list = JSONObject.parseArray(authority, String.class);
                    list.forEach(a -> {
                        authorities.add(new SimpleGrantedAuthority(a));
                    });
                }*/
                if (StringUtils.isNotBlank(username)) {
                    //踩坑提醒，此处password不能为null
                    User user = new User(username, "", authorities);
                    return new UsernamePasswordAuthenticationToken(user, null, authorities);
                }
                System.out.println("11111111111111111111111111111111111111111111111111");
            } catch (Exception e) {
                System.out.println("222222222222222222222222222222222222222222222");
                ResponseUtil.out(response, ResponseUtil.resultMap(false, 500, "登录已失效，请重新登录"));
            }
        }
        System.out.println("33333333333333333333333333333333333333333333333");
        return null;
    }
}
